/**
 * 
 */
package graph;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import util.MathUtil;

/**
 * @author xiaohui
 * 
 */
public class GraphNode implements SpatialSearchTreeObject {
	private int id;
	/**
	 * x-coordinate.
	 */
	protected double x = 0;
	/**
	 * y-coordinate.
	 */
	protected double y = 0;

	private Set<Integer> routeIds;

	/**
	 * Constructor.
	 * 
	 * @param id
	 *            id of the node
	 * @param x
	 *            x-coordinate
	 * @param y
	 *            y-coordinate
	 */
	public GraphNode(int id, double x, double y) {
		this.id = id;
		this.x = x;
		this.y = y;
		this.routeIds = new HashSet<Integer>();
	}

	public GraphNode(int id, GraphNode graphNode) {
		this.id = id;
		this.x = graphNode.x;
		this.y = graphNode.y;
		this.routeIds = new HashSet<Integer>();
	}

	public GraphNode(int id) {
		this.id = id;
		this.x = -1;
		this.y = -1;
		// this.routeIds = new ArrayList<Integer>();
	}

	@Override
	public MBR getMBR() {
		return new MBR(x, y, 0, 0);
	}

	@Override
	public int getNumOfDimensions() {
		return 2;
	}

	@Override
	public double computeDistanceTo(double[] point) {
		return MathUtil.computeEuclideanDistance(x, y, point[0], point[1]);
	}

	@Override
	public boolean contains(MBR rect) {
		if (rect == null)
			return false;
		else
			return getMBR().contains(rect);
	}

	@Override
	public int getId() {
		return id;
	}

	@Override
	public boolean intersects(Object obj) {
		if (obj instanceof GraphNode) {
			return getMBR().intersects(((GraphNode) obj).getMBR());
		} else if (obj instanceof GraphEdge) {
			return getMBR().intersects(((GraphEdge) obj).getMBR());
		} else
			return false;
	}

	@Override
	public boolean intersects(MBR r) {
		return getMBR().intersects(r);
	}

	@Override
	public boolean isContainedBy(MBR rect) {
		return (rect.contains(getMBR()));
	}

	@Override
	public boolean isOfSameType(SpatialSearchTreeObject obj) {
		if (obj instanceof GraphNode)
			return true;
		else
			return false;
	}

	public String toString() { // Always a good idea for debuging
		// JUNG2 makes good use of these.
		return "GN" + id + " (" + x + "," + y + ")";
	}

	/**
	 * 
	 * @param graphnode
	 * @return distance
	 */
	public double distance(GraphNode gn) {
		return MathUtil.computeEuclideanDistance(x, y, gn.x, gn.y);
	}

	public void addRid(int routeId) {
		if (this.routeIds == null)
			this.routeIds = new HashSet<Integer>();
		this.routeIds.add(routeId);
	}

	
	public Set<Integer> getRouteIds() {
		return routeIds;
	}

	public void setRouteIds(Set<Integer> routeIds) {
		this.routeIds = routeIds;
	}

	public double getX() {
		return x;
	}

	public void setX(double x) {
		this.x = x;
	}

	public double getY() {
		return y;
	}

	public void setY(double y) {
		this.y = y;
	}

}
